#!/bin/bash
# This script gathers some basic information about the processes running
# on the system, including a JVM thread dump of the HMC "manager" JVM.
# It attempts to determine whether a zSeries or pSeries HMC is running.
# You must be logged in as root to run this script.

# Make sure we're root
me=$(whoami)                # Current user's login name
if [ $me != "root" ]; then
   echo "You must be logged in as root to run this script; you are currently logged in as $me."
   exit 1
fi

zhmctopscript='startmanager'  # Top-level zSeries HMC manager startup script
phmctopscript='runccfw'       # Top-level pSeries HMC manager startup script
topscripts="$zhmctopscript $phmctopscript"
sleepamount='10'  # How long to wait for JVM thread dump, in seconds

# Names of output files created by this script.  Include PID for uniqueness.
logfn="/tmp/hmcdebuginfo.$$.log"
tarfn="/tmp/hmcdebuginfo.$$.tgz"

echo "Information gathered by hmcdebuginfo run at $(date) will be placed in $logfn"
# Start a new log file and gather some system info
echo "Gathering info from hmcdebuginfo run at $(date)" > $logfn
pstree -lp >> $logfn
top -bn1 >> $logfn
free >> $logfn
  
# Determine which HMC (zSeries or pSeries) is running
for topscript in $topscripts; do
   line=$(pstree -lp|grep $topscript)
   if [ -n "$line" ]; then
      break
   fi
done

if [ -z "$line" ]; then
   echo "Unable to find the top-level script in pstree output."
   echo "The HMC does not appear to be running at this time.  Exiting..."
   exit 2
fi

if [ $topscript == $zhmctopscript ]; then  # zSeries HMC is running
   hmctopdir='/console'
   managerlogin='hmcmanager'
else                                       # pSeries HMC is running
   hmctopdir='/opt/ccfw'                     
   managerlogin='ccfw'
fi
   
# Remove all characters up to the command that follows the top-level script
temp=${line#*$topscript(*)---}

# Get and verify the name of the command that follows the top-level script
cmd=${temp%%(*}
if [ $cmd != "su" ]; then
   echo "$topscript command is not followed by 'su' command in pstree output."
   echo "Unexpected cmd/pid tree structure.  Exiting..."
   exit 3
fi

# Remove all characters up to the command that follows the 'su' command
temp=${temp#*$cmd(*)---}

# Get and verify the name of the command that follows the 'su' command
cmd=${temp%%(*}
if [ $cmd != "java" ]; then
   echo "'su' command is not followed by 'java' command in pstree output."
   echo "Unexpected cmd/pid tree structure.  Exiting..."
   exit 4
fi

# Get the PID for that process (the manager JVM)
pid=${temp##$cmd(}
pid=${pid%%)*}

# Send it a SIGQUIT signal to cause it to take a thread dump
echo "About to send the SIGQUIT signal to $cmd process with PID $pid..."
kill -s SIGQUIT $pid
if [ $? != 0 ]; then
   echo "Attempt to signal PID $pid failed with exit status $?"
   echo "You must be logged in as root or $managerlogin to run this script."
   exit 5
else
   echo "Sleeping for $sleepamount seconds while the JVM processes the thread dump request..."
   sleep ${sleepamount}s
fi

datafiles="$logfn $hmctopdir/javacore* $hmctopdir/data/iqzdtrac.trm $hmctopdir/data/iqyy*.log"
if [ $topscript == $zhmctopscript ]; then  # zSeries HMC is running
   datafiles="$datafiles /var/log/manager.log /var/log/client.log"
fi
ls -lt $datafiles $hmctopdir/core* >> $logfn 2>&1

echo "About to create tar file containing debugging information..."
tar czf $tarfn $datafiles
if [ -f $tarfn ]; then
   echo "Tar file $tarfn has been created."
else
   echo "Attempt to create tar file $targn failed with exit status $?"
   exit 6
fi

exit 0
